//导入模块
//服务器构造函数
var express = require('express');
//处理文件上传
var multer = require('multer');
//处理post请求的参数到body对象中

var bodyParser = require('body-parser');
//处理缓存 cookies 到 cookie 对象中
var cookParser = require('cookie-parser');
//处理文件 io
var fs = require('fs');

//创建服务器对象
var app = express();

//配置存储上传文件 storage//destination:文件保存位置
var storage=multer.diskStorage({
	
	destination:'www/uploads',
	filename:function (req,res,callback) {
		var petname =req.cookies.petname;
		callback(null,petname + '.jpg');
	}
	
});
var upload = multer({storage});


//配置静态文件夹
app.use(express.static('www'));
//post解析
app.use(bodyParser.urlencoded({
	extended: true
}));
//解析cookie对象
app.use(cookParser());

///////////////////设置跨域访问//////////////////////////
app.all('*', function(req, res, next) {
    res.header("Access-Control-Allow-Origin", "*");
    res.header("Access-Control-Allow-Headers", "X-Requested-With");
    res.header("Access-Control-Allow-Methods","PUT,POST,GET,DELETE,OPTIONS");
    res.header("X-Powered-By",' zqs')
    res.header("Content-Type", "application/json;charset=utf-8");
    next();
});

//********************************************

/**************************注册**********************************************/
app.post('/user/register', function(req, res) {
	console.log(req.body);
	//先判断有没有user文件夹
	fs.exists('users', function(exi) {
		if(exi) {

			//存在
			writeFile();

		} else {
			//不存在
			//创建users文件夹(mkdirSync同步:没有回调函数，mkdir异步：有回调函数)
			fs.mkdir('users', function(err) {

				if(err) {
					//创建失败
					res.status(200).json({
						code: 0,
						message: '系统创建文件夹失败！'
					});
				} else {
					//创建成功（写入）
					writeFile();

				}

			});

		}
	});

	//封装一个写入注册信息的方法
	function writeFile() {

		//判断用户是否已经注册过
		//		var fileName=`users/${req.body.petname}.txt`;
		var fileName = 'users/' + req.body.petname + '.txt';
		fs.exists(fileName, function(exi) {

			if(exi) {
				//(文件)用户已经存在，
				res.status(200).json({
					code: 2,
					message: '用户名已经存在，请更改用户名，重新注册'

				})
			} else {
				//在 body 中加入 ip 和 time
				req.body.ip = req.ip;
				req.body.time = new Date();
				//未被注册，创建用户信息文件
				fs.writeFile(fileName, JSON.stringify(req.body), function(err) {

					if(err) {
						//写入失败
						res.status(200).json({
							code: 1,
							message: '系统错误写入文件失败'
						});
					} else {
						//保存成功
						res.status(200).json({
							code: 3,
							message: '注册成功'
						});

					}

				});
			}

		});
	}

});

/**************************登录**********************************************/
app.post('/user/login', function(req, res) {

	//根据 req.petname 去 user 文件夹中匹配文件
	var fileName = 'users/' + req.body.petname + '.txt';
	console.log(fileName);
	fs.exists(fileName, function(exi) {
		if(exi) {
			//req.petname 去 user 读取
			fs.readFile(fileName, function(err, data) {
				if(err) {
					//读取失败
					//返回系统错误code=1
					res.status(200).json({
						code: 1,
						message: '系统错误，读取文件失败'
					});

				} else {
					//读取成功
					//比较 req.password==读出的那个密码
					var user = JSON.parse(data); //字符串转换成对象

					//把petname 设置到 cookie(把petname 存储在当前网站内)
					//					1.有利于下次登录，2.保存用户信息
					var expires = new Date();
					expires.setMonth(expires.getMonth() + 1);
					console.log(expires);

					res.cookie('petname', req.body.petname, {
						'masAge': 90000
					});

					//					res.cookie('petname', req.body.petname, {expires});

					if(req.body.password == user.password) {
						//登录成功
						res.status(200).json({
							code: 3,
							message: '登录成功'

						});

					} else {
						res.status(200).json({
							code: 2,
							message: '密码错误'

						});

					}

				}
			});
		} else {

			//匹配不到
			//返回用户不存在 code=0
			res.status(200).json({

				code: 0,
				message: '用户不存在'

			});

		}
	});

});

/********************提问*****************************/

//app.use(haveCookies);//请求处理管线，任何请求传来都要经过这个函数处理
app.post('/question/ask', function(req, res) {
	//注意，cookie是自动会传给服务器的
	//判断有没有cookie 把petname 传递过来
	console.log('提问者：' + req.cookies.petname);
	if(!req.cookies.petname) {
		//比如确实登录了，但是某些清除垃圾的软件吧存储的cookie清除了
		//或者用户自己清除了或 cookie有效期到了
		res.status(200).json({
			code: 0,
			message: '登录异常，请重新登录'

		});
		return;

	}
	//判断 question 文件夹是否存在
	fs.exists('question', function(exi) {

		if(exi) {
			//存在
			writeFile();

		} else {

			//不存在（创建文件夹）
			fs.mkdir('question', function(err) {

				if(err) {

					//c创建文件夹失败
					res.status(200).json({
						code: 0,
						message: '系统创建文件夹失败'

					});
				} else {

					//创建成功(写入文件)
					writeFile();
				}

			});

		}

	});

	//封装写入问题的方法
	function writeFile() {
		//生成提问问题的文件名
		var date = new Date();
		var fileName = 'question/' + date.getTime() + '.txt';
		req.body.petname = req.cookies.petname;
		//这里可以直接添加属性到body中
		req.body.ip = req.ip;
		req.body.time = date;
		var content=req.body.content;
	//XSS(Corss Site Scripting 跨站脚本攻击)恶意攻击者往Web页面里插入恶意Script代码，当用户浏览该页之时，嵌入其中Web里面的Script代码会被执行，从而达到恶意攻击用户的目的。
	//为了防止XSS攻击，用户在提交数据的时候恶意嵌入<script>代码
	 content = content.replace(/</g,'&lt;');
	 content = content.replace(/>/g,'&gt;');
	req.body.content=content;
		
		//写入文件
		fs.writeFile(fileName, JSON.stringify(req.body), function(err) {
			if(err) {
				//写入失败
				res.status(200).json({
					code: 1,
					message: '系统错误，写入文件失败'

				});
			} else {
				//写入成功
				res.status(200).json({

					code: 2,
					message: '提交问题成功'
				});
			}

		});

	}

});

/******************************退出登录**********************************/
app.get('/user/logout', function(req, res) {
	console.log('退出登录');
	//清除 cookie 中的 petname
	res.clearCookie('petname');
	//	res.cookie('petname','');
	res.status(200).json({

		code: 1,
		message: '退出登录成功'

	});

});
/***********************首页数据************************************************/

app.get('/question/all', function(req, res) {
	//返回所以的问题（包含回答）
	fs.readdir('question', function(err, files) {
		//		console.log(files); //[ '1486957075936.txt', '1486957190501.txt', '1486972668900.txt' ]

		if(err) {
			//读取文件失败
			res.status(200).json({
				code: 0,
				message: '读取文件失败'

			});

		} else {
			//读取文件成功
			//数组反序，目的：让最新提问的问题排在最前面
			files = files.reverse();
			//创建一个数组容器，存放所有的问题对象
			var questions = [];
			//方法一，用for读取文件
			//			for (var i = 0; i < files.length; i++) {
			//				var file= files[i];
			//				var filePath ='question/' +file;
			//				//同步读取文件，异步读取会导致请求回发时，文件还没读取完成
			//				var data=fs.readFileSync(filePath);
			//				var obj=JSON.parse(data);
			//					questions.push(obj);
			//			}
			//			res.status(200).json(questions);

			//方法二：用递归来遍历文件，用异步读取文件
			var i = 0;

			function readFile() {

				if(i < files.length) {
					var file = files[i];
					var filePath = 'question/' + file;
					fs.readFile(filePath, function(err, data) {
						if(!err) {
							var obj = JSON.parse(data);
							questions.push(obj);
							i++;
							readFile();
						}
					});

				} else {
					res.status(200).json(questions);
				}

			}
			readFile();

		}
	});

});

/*****************************回答问题************************************************/
app.post('/question/answer',function (req,res) {

	
	//判断登录状态
	var petname =req.cookies.petname;
	if (!petname) {
		res.status(200).json({
			
			code:0,
			message:'登录异常，请重新登录'
		});
		return;
	}

	//先取出要回答的内容
	var question=req.cookies.question;
	var filePath='question/' +question +'.txt';
	
	fs.readFile(filePath,function (err,data) {
		
		if (!err) {
			
			var dataObj=JSON.parse(data);
			//判断有没有 answers 属性（有：之前回答过    没有：之前没回答过）
//			console.log(dataObj.answers) ;
			if (!dataObj.answers) {
				console.log('没有回答过');
			dataObj.answers=[];
			}
			//把答案对象{ip,time,petname,content} push进去
			req.body.content=req.body.content.replace(/</g,'&lt;');
			req.body.content=req.body.content.replace(/>/g,'&gt;');
			req.body.ip=req.ip;
			req.body.question=question;
			req.body.time=new Date();
			req.body.petname=petname;
			//把答案push到answers中,是添加，不是覆盖
			dataObj.answers.push(req.body);
			
			//修改过后重新写入
			fs.writeFile(filePath,JSON.stringify(dataObj),function (err) {
				if (err) {
					//写入失败
					res.status(200).json({
						code:1,
						message:'系统错误，写入文件失败'
						
					});
				}else{
					//写入成功
					
					res.status(200).json({
						
						code:2,
						message:'提交答案成功'
						
					});
					
				}
			});
			
			
		}
		
	});
	
});


/*************************上传头像*****************************************************/
//upload.Array('photo',6);//多张    单张single   photo是前端表单中file的name属性
app.post('/user/photo',upload.single('photo'),function (req,res) {
	
	res.status(200).json({
		
		code:0,
		message:'上传头像成功'
	});
	
});



//添加端口和启动服务器
app.listen(3000, function() {
	console.log('问答系统服务器启动中。。。');
});